<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">


<html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    
    <title>Slide and Pin Joint Demo Step by Step &mdash; pymunk 4.0.0 documentation</title>
    
    <link rel="stylesheet" href="../_static/pymunk.css" type="text/css" />
    <link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
    
    <script type="text/javascript">
      var DOCUMENTATION_OPTIONS = {
        URL_ROOT:    '../',
        VERSION:     '4.0.0',
        COLLAPSE_INDEX: false,
        FILE_SUFFIX: '.html',
        HAS_SOURCE:  true
      };
    </script>
    <script type="text/javascript" src="../_static/jquery.js"></script>
    <script type="text/javascript" src="../_static/underscore.js"></script>
    <script type="text/javascript" src="../_static/doctools.js"></script>
    <link rel="shortcut icon" href="../_static/pymunk_favicon.ico"/>
    <link rel="top" title="pymunk 4.0.0 documentation" href="../index.html" />
    <link rel="up" title="Tutorials" href="../tutorials.html" />
    <link rel="next" title="Advanced" href="../advanced.html" />
    <link rel="prev" title="Arrows and other pointy sticky things" href="Arrows.html" /> 
  </head>
  <body>
    <div class="related">
      <h3>Navigation</h3>
      <ul>
        <li class="right" style="margin-right: 10px">
          <a href="../genindex.html" title="General Index"
             accesskey="I">index</a></li>
        <li class="right" >
          <a href="../py-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li class="right" >
          <a href="../advanced.html" title="Advanced"
             accesskey="N">next</a> |</li>
        <li class="right" >
          <a href="Arrows.html" title="Arrows and other pointy sticky things"
             accesskey="P">previous</a> |</li>
        <li><a href="../index.html">pymunk 4.0.0 documentation</a> &raquo;</li>
          <li><a href="../tutorials.html" accesskey="U">Tutorials</a> &raquo;</li> 
      </ul>
    </div>  

    <div class="document">
      <div class="documentwrapper">
        <div class="bodywrapper">
          <div class="body">
            
  <div class="section" id="slide-and-pin-joint-demo-step-by-step">
<h1>Slide and Pin Joint Demo Step by Step<a class="headerlink" href="#slide-and-pin-joint-demo-step-by-step" title="Permalink to this headline">¶</a></h1>
<p>This is a step by step tutorial explaining the demo demo_slide_and_pinjoint.py
included in pymunk. You will find a screenshot of it in the list of
<a class="reference internal" href="../examples.html#id1"><em>examples</em></a>.
It is probably a good idea to have the file near by if I
miss something in the tutorial or something is unclear.</p>
<div class="section" id="before-we-start">
<h2>Before we start<a class="headerlink" href="#before-we-start" title="Permalink to this headline">¶</a></h2>
<p>For this tutorial you will need:</p>
<ul class="simple">
<li>Python (of course)</li>
<li>pygame (found at www.pygame.org)</li>
<li>pymunk</li>
</ul>
<p>Pygame is required for this tutorial and some of the included demos, but it
is not required to run just pymunk. Pymunk should work just fine with other
similar libraries as well, for example you could easily translate this
tutorial to use pyglet instead.</p>
<p>Pymunk is built on top of the 2d physics library Chipmunk. Chipmunk itself
is written in C meaning pymunk need to call into the c code. The ctypes
library helps with this, however if you are on a platform that I haven&#8217;t been
able to compile it on you might have to do it yourself. The good news is that
it is very easy to do!</p>
<p>When you have pymunk installed, try to import it from the python prompt to
make sure it works and can be imported:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="gp">&gt;&gt;&gt; </span><span class="kn">import</span> <span class="nn">pymunk</span>
</pre></div>
</div>
<p>If you get an error message it usually is because pymunk could not find the
chipmunk library because it was not compiled (should not happen on windows and
ubuntu, as pymunk ships with the code compiled for those two). To compile
chipmunk, do</p>
<div class="highlight-python"><pre>&gt; python setup.py build_chipmunk
&gt; python setup.py install</pre>
</div>
<p>More information on installation can be found here:
<a class="reference internal" href="../installation.html#id1"><em>Installation</em></a></p>
<p>If it doesnt work or you have some kind of problem, feel free to write a post
in the chipmunk forum, contact me directly or add your problem to the issue
tracker: <a class="reference internal" href="../index.html#id1"><em>Contact &amp; Support</em></a></p>
</div>
<div class="section" id="an-empty-simulation">
<h2>An empty simulation<a class="headerlink" href="#an-empty-simulation" title="Permalink to this headline">¶</a></h2>
<p>Ok, lets start.
Chipmunk (and therefore pymunk) has a couple of central concepts, which is
explained pretty good in this citation from the Chipmunk docs:</p>
<dl class="docutils">
<dt>rigid bodies</dt>
<dd>A rigid body holds the physical properties of an object. (mass, position, rotation, velocity, etc.) It does not have a shape by itself. If you&#8217;ve done physics with particles before, rigid bodies differ mostly in that they are able to rotate.</dd>
<dt>collision shapes</dt>
<dd>By attaching shapes to bodies, you can define the a body&#8217;s shape. You can attach many shapes to a single body to define a complex shape, or none if it doesn&#8217;t require a shape.</dd>
<dt>constraints/joints</dt>
<dd>You can attach joints between two bodies to constrain their behavior.</dd>
<dt>spaces</dt>
<dd>Spaces are the basic simulation unit in Chipmunk. You add bodies, shapes and joints to a space, and then update the space as a whole._</dd>
</dl>
<p>The documentation for chipmunk can be found here:
<a class="reference external" href="http://chipmunk-physics.net/release/ChipmunkLatest-Docs/">http://chipmunk-physics.net/release/ChipmunkLatest-Docs/</a>
It is for the c-library but is a good complement to the pymunk documentation.</p>
<p>The API documentation for pymunk can be found here: <a class="reference internal" href="../pymunk.html"><em>API Reference</em></a>.</p>
<p>Anyway, we are now ready to write some code:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">import</span> <span class="nn">sys</span>
<span class="kn">import</span> <span class="nn">pygame</span>
<span class="kn">from</span> <span class="nn">pygame.locals</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">from</span> <span class="nn">pygame.color</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">import</span> <span class="nn">pymunk</span> <span class="c">#1</span>

<span class="k">def</span> <span class="nf">main</span><span class="p">():</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">init</span><span class="p">()</span>
    <span class="n">screen</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_mode</span><span class="p">((</span><span class="mi">600</span><span class="p">,</span> <span class="mi">600</span><span class="p">))</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_caption</span><span class="p">(</span><span class="s">&quot;Joints. Just wait and the L will tip over&quot;</span><span class="p">)</span>
    <span class="n">clock</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">time</span><span class="o">.</span><span class="n">Clock</span><span class="p">()</span>
    <span class="n">running</span> <span class="o">=</span> <span class="bp">True</span>

    <span class="n">space</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Space</span><span class="p">()</span> <span class="c">#2</span>
    <span class="n">space</span><span class="o">.</span><span class="n">gravity</span> <span class="o">=</span> <span class="p">(</span><span class="mf">0.0</span><span class="p">,</span> <span class="o">-</span><span class="mf">900.0</span><span class="p">)</span>

    <span class="k">while</span> <span class="n">running</span><span class="p">:</span>
        <span class="k">for</span> <span class="n">event</span> <span class="ow">in</span> <span class="n">pygame</span><span class="o">.</span><span class="n">event</span><span class="o">.</span><span class="n">get</span><span class="p">():</span>
            <span class="k">if</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">QUIT</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">elif</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">KEYDOWN</span> <span class="ow">and</span> <span class="n">event</span><span class="o">.</span><span class="n">key</span> <span class="o">==</span> <span class="n">K_ESCAPE</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>

        <span class="n">screen</span><span class="o">.</span><span class="n">fill</span><span class="p">(</span><span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;white&quot;</span><span class="p">])</span>

        <span class="n">space</span><span class="o">.</span><span class="n">step</span><span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">50.0</span><span class="p">)</span> <span class="c">#3</span>

        <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">flip</span><span class="p">()</span>
        <span class="n">clock</span><span class="o">.</span><span class="n">tick</span><span class="p">(</span><span class="mi">50</span><span class="p">)</span>

<span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&#39;__main__&#39;</span><span class="p">:</span>
    <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">(</span><span class="n">main</span><span class="p">())</span>
</pre></div>
</div>
<p>The code will display a blank window, and will run a physics simulation of an empty space.</p>
<ol class="arabic simple">
<li>We need to import pymunk in order to use it...</li>
</ol>
<p>#. We then create a space and set its gravity to something good. Remember
that what is important is what looks good on screen, not what the real
world value is. -900 will make a good looking simulation, but feel free
to experiment when you have the full code ready.</p>
<p>#. In our game loop we call the step() function on our space. The step
function steps the simulation one step forward in time. Note: It is best
to keep the stepsize constant and not adjust it depending on the
framrate. The physic simulation will work much better with a constant step
size.</p>
</div>
<div class="section" id="falling-balls">
<h2>Falling balls<a class="headerlink" href="#falling-balls" title="Permalink to this headline">¶</a></h2>
<p>The easiest shape to handle (and draw) is the circle. Therefore our next
step is to make a ball spawn once in while. In most demos all code is in one
big pile in the main() function as they are so small and easy, but I will
extract some methods in this tutorial to make it more easy to follow. First,
a function to add a ball to a space:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">add_ball</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="n">mass</span> <span class="o">=</span> <span class="mi">1</span>
    <span class="n">radius</span> <span class="o">=</span> <span class="mi">14</span>
    <span class="n">inertia</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">moment_for_circle</span><span class="p">(</span><span class="n">mass</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="n">radius</span><span class="p">)</span> <span class="c"># 1</span>
    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">(</span><span class="n">mass</span><span class="p">,</span> <span class="n">inertia</span><span class="p">)</span> <span class="c"># 2</span>
    <span class="n">x</span> <span class="o">=</span> <span class="n">random</span><span class="o">.</span><span class="n">randint</span><span class="p">(</span><span class="mi">120</span><span class="p">,</span><span class="mi">380</span><span class="p">)</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="n">x</span><span class="p">,</span> <span class="mi">550</span> <span class="c"># 3</span>
    <span class="n">shape</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Circle</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">radius</span><span class="p">)</span> <span class="c"># 4</span>
    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">shape</span><span class="p">)</span> <span class="c"># 5</span>
    <span class="k">return</span> <span class="n">shape</span>
</pre></div>
</div>
<p>#. All bodies must have their moment of inertia set. If our object is a
normal ball we can use the predefined function moment_for_circle to
calculate it given its mass and radius. However, you could also select a
value by experimenting with what looks good for your simulation.</p>
<ol class="arabic simple">
<li>After we have the inertia we can create the body of the ball.</li>
<li>And we set its position</li>
</ol>
<p>#. And in order for it to collide with things, it needs to have one
(or many) collision shape(s).</p>
<p>#. Finally we add the body and shape to the space to include it in our
simulation.</p>
<p>Now that we can create balls we want to display them:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">):</span>
    <span class="n">p</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">x</span><span class="p">),</span> <span class="mi">600</span><span class="o">-</span><span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">y</span><span class="p">)</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;blue&quot;</span><span class="p">],</span> <span class="n">p</span><span class="p">,</span> <span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">radius</span><span class="p">),</span> <span class="mi">2</span><span class="p">)</span>
</pre></div>
</div>
<p>As I have used pygame in this example, we can use the draw.circle function
to draw the balls. But first we must convert the position of the ball. We
earlier set the gravity to -900 (that is, it will point down the y axis).
Pygame thinks 0,0 is at the top left of the screen, with y increasing
downwards. So we need to make a simple conversion of the y value.</p>
<p>An alternative way to handle the display would have been to use the
pygame_util.draw_space function that is included in pymunk. However, in this
tutorial I wanted to show how to draw things yourself as you are likley to
want that in your own code anyway at some point.</p>
<p>With these two functions and a little code to spawn balls you should see a
couple of balls falling. Yay!</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">import</span> <span class="nn">sys</span><span class="o">,</span> <span class="nn">random</span>
<span class="kn">import</span> <span class="nn">pygame</span>
<span class="kn">from</span> <span class="nn">pygame.locals</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">from</span> <span class="nn">pygame.color</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">import</span> <span class="nn">pymunk</span>

<span class="c">#def add_ball(space):</span>
<span class="c">#def draw_ball(screen, ball):</span>

<span class="k">def</span> <span class="nf">main</span><span class="p">():</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">init</span><span class="p">()</span>
    <span class="n">screen</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_mode</span><span class="p">((</span><span class="mi">600</span><span class="p">,</span> <span class="mi">600</span><span class="p">))</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_caption</span><span class="p">(</span><span class="s">&quot;Joints. Just wait and the L will tip over&quot;</span><span class="p">)</span>
    <span class="n">clock</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">time</span><span class="o">.</span><span class="n">Clock</span><span class="p">()</span>
    <span class="n">running</span> <span class="o">=</span> <span class="bp">True</span>

    <span class="n">space</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Space</span><span class="p">()</span>
    <span class="n">space</span><span class="o">.</span><span class="n">gravity</span> <span class="o">=</span> <span class="p">(</span><span class="mf">0.0</span><span class="p">,</span> <span class="o">-</span><span class="mf">900.0</span><span class="p">)</span>

    <span class="n">balls</span> <span class="o">=</span> <span class="p">[]</span>

    <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">10</span>
    <span class="k">while</span> <span class="n">running</span><span class="p">:</span>
        <span class="k">for</span> <span class="n">event</span> <span class="ow">in</span> <span class="n">pygame</span><span class="o">.</span><span class="n">event</span><span class="o">.</span><span class="n">get</span><span class="p">():</span>
            <span class="k">if</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">QUIT</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">elif</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">KEYDOWN</span> <span class="ow">and</span> <span class="n">event</span><span class="o">.</span><span class="n">key</span> <span class="o">==</span> <span class="n">K_ESCAPE</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>

        <span class="n">ticks_to_next_ball</span> <span class="o">-=</span> <span class="mi">1</span>
        <span class="k">if</span> <span class="n">ticks_to_next_ball</span> <span class="o">&lt;=</span> <span class="mi">0</span><span class="p">:</span>
            <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">25</span>
            <span class="n">ball_shape</span> <span class="o">=</span> <span class="n">add_ball</span><span class="p">(</span><span class="n">space</span><span class="p">)</span>
            <span class="n">balls</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">ball_shape</span><span class="p">)</span>

        <span class="n">screen</span><span class="o">.</span><span class="n">fill</span><span class="p">(</span><span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;white&quot;</span><span class="p">])</span>

        <span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls</span><span class="p">:</span>
            <span class="n">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">)</span>

        <span class="n">space</span><span class="o">.</span><span class="n">step</span><span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">50.0</span><span class="p">)</span>

        <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">flip</span><span class="p">()</span>
        <span class="n">clock</span><span class="o">.</span><span class="n">tick</span><span class="p">(</span><span class="mi">50</span><span class="p">)</span>

<span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&#39;__main__&#39;</span><span class="p">:</span>
    <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">(</span><span class="n">main</span><span class="p">())</span>
</pre></div>
</div>
</div>
<div class="section" id="a-static-l">
<h2>A static L<a class="headerlink" href="#a-static-l" title="Permalink to this headline">¶</a></h2>
<p>Falling balls are quite boring. We don&#8217;t see any physics simulation except
basic gravity, and everyone can do gravity without help from a physics
library. So lets add something the balls can land on, two static lines
forming an L. As with the balls we start with a function to add an L to the
space:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">add_static_L</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span> <span class="c"># 1</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span> <span class="mi">300</span><span class="p">)</span>
    <span class="n">l1</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">255</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="mi">5</span><span class="p">)</span> <span class="c"># 2</span>
    <span class="n">l2</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">50</span><span class="p">),</span> <span class="mi">5</span><span class="p">)</span>

    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">l1</span><span class="p">,</span> <span class="n">l2</span><span class="p">)</span> <span class="c"># 3</span>
    <span class="k">return</span> <span class="n">l1</span><span class="p">,</span><span class="n">l2</span>
</pre></div>
</div>
<ol class="arabic simple">
<li>We create a &#8220;static&#8221; body. The important step is to never add it to the space. Note how static bodies are created by not passing any arguments to the Body constructor.</li>
<li>A line shaped shape is created here.</li>
<li>Again, we only add the segments, not the body to the space.</li>
</ol>
<p>Next we add a function to draw the L shape:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">draw_lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">lines</span><span class="p">):</span>
    <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span>
        <span class="n">body</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">body</span>
        <span class="n">pv1</span> <span class="o">=</span> <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">+</span> <span class="n">line</span><span class="o">.</span><span class="n">a</span><span class="o">.</span><span class="n">rotated</span><span class="p">(</span><span class="n">body</span><span class="o">.</span><span class="n">angle</span><span class="p">)</span> <span class="c"># 1</span>
        <span class="n">pv2</span> <span class="o">=</span> <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">+</span> <span class="n">line</span><span class="o">.</span><span class="n">b</span><span class="o">.</span><span class="n">rotated</span><span class="p">(</span><span class="n">body</span><span class="o">.</span><span class="n">angle</span><span class="p">)</span>
        <span class="n">p1</span> <span class="o">=</span> <span class="n">to_pygame</span><span class="p">(</span><span class="n">pv1</span><span class="p">)</span> <span class="c"># 2</span>
        <span class="n">p2</span> <span class="o">=</span> <span class="n">to_pygame</span><span class="p">(</span><span class="n">pv2</span><span class="p">)</span>
        <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;lightgray&quot;</span><span class="p">],</span> <span class="bp">False</span><span class="p">,</span> <span class="p">[</span><span class="n">p1</span><span class="p">,</span><span class="n">p2</span><span class="p">])</span>
</pre></div>
</div>
<p>#. In order to get the position with the line rotation we use this
calculation. line.a is the first endpoint of the line, line.b the second.
At the moment the lines are static, so we don&#8217;t really have to do this extra
calculation, but we will soon make them move and rotate.</p>
<p>#. This is a little function to convert coordinates from pymunk to pygame
world. Now that we have it we can use it in the draw_ball() function as
well. We want to flip the y coordinate (-p.y), and then offset it with the
screen height (+600). It looks like this:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">to_pygame</span><span class="p">(</span><span class="n">p</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Small hack to convert pymunk to pygame coordinates&quot;&quot;&quot;</span>
    <span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">p</span><span class="o">.</span><span class="n">x</span><span class="p">),</span> <span class="nb">int</span><span class="p">(</span><span class="o">-</span><span class="n">p</span><span class="o">.</span><span class="n">y</span><span class="o">+</span><span class="mi">600</span><span class="p">)</span>
</pre></div>
</div>
<p>We add a call to add_static_L() and one to draw_lines() and now we should
see an inverted L shape in the middle will balls spawning and hitting the
shape.</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">import</span> <span class="nn">sys</span><span class="o">,</span> <span class="nn">random</span>
<span class="kn">import</span> <span class="nn">pygame</span>
<span class="kn">from</span> <span class="nn">pygame.locals</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">from</span> <span class="nn">pygame.color</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">import</span> <span class="nn">pymunk</span> <span class="kn">as</span> <span class="nn">pm</span>
<span class="kn">import</span> <span class="nn">math</span>

<span class="c">#def to_pygame(p):</span>
<span class="c">#def add_ball(space):</span>
<span class="c">#def draw_ball(screen, ball):</span>
<span class="c">#def add_static_l(space):</span>
<span class="c">#def draw_lines(screen, lines):</span>

<span class="k">def</span> <span class="nf">main</span><span class="p">():</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">init</span><span class="p">()</span>
    <span class="n">screen</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_mode</span><span class="p">((</span><span class="mi">600</span><span class="p">,</span> <span class="mi">600</span><span class="p">))</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_caption</span><span class="p">(</span><span class="s">&quot;Joints. Just wait and the L will tip over&quot;</span><span class="p">)</span>
    <span class="n">clock</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">time</span><span class="o">.</span><span class="n">Clock</span><span class="p">()</span>
    <span class="n">running</span> <span class="o">=</span> <span class="bp">True</span>

    <span class="n">space</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Space</span><span class="p">()</span>
    <span class="n">space</span><span class="o">.</span><span class="n">gravity</span> <span class="o">=</span> <span class="p">(</span><span class="mf">0.0</span><span class="p">,</span> <span class="o">-</span><span class="mf">900.0</span><span class="p">)</span>

    <span class="n">lines</span> <span class="o">=</span> <span class="n">add_static_L</span><span class="p">(</span><span class="n">space</span><span class="p">)</span>
    <span class="n">balls</span> <span class="o">=</span> <span class="p">[]</span>

    <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">10</span>
    <span class="k">while</span> <span class="n">running</span><span class="p">:</span>
        <span class="k">for</span> <span class="n">event</span> <span class="ow">in</span> <span class="n">pygame</span><span class="o">.</span><span class="n">event</span><span class="o">.</span><span class="n">get</span><span class="p">():</span>
            <span class="k">if</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">QUIT</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">elif</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">KEYDOWN</span> <span class="ow">and</span> <span class="n">event</span><span class="o">.</span><span class="n">key</span> <span class="o">==</span> <span class="n">K_ESCAPE</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>

        <span class="n">ticks_to_next_ball</span> <span class="o">-=</span> <span class="mi">1</span>
        <span class="k">if</span> <span class="n">ticks_to_next_ball</span> <span class="o">&lt;=</span> <span class="mi">0</span><span class="p">:</span>
            <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">25</span>
            <span class="n">ball_shape</span> <span class="o">=</span> <span class="n">add_ball</span><span class="p">(</span><span class="n">space</span><span class="p">)</span>
            <span class="n">balls</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">ball_shape</span><span class="p">)</span>

        <span class="n">screen</span><span class="o">.</span><span class="n">fill</span><span class="p">(</span><span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;white&quot;</span><span class="p">])</span>

        <span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls</span><span class="p">:</span>
            <span class="n">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">)</span>

        <span class="n">draw_lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">lines</span><span class="p">)</span>

        <span class="n">space</span><span class="o">.</span><span class="n">step</span><span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">50.0</span><span class="p">)</span>

        <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">flip</span><span class="p">()</span>
        <span class="n">clock</span><span class="o">.</span><span class="n">tick</span><span class="p">(</span><span class="mi">50</span><span class="p">)</span>

<span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&#39;__main__&#39;</span><span class="p">:</span>
    <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">(</span><span class="n">main</span><span class="p">())</span>
</pre></div>
</div>
</div>
<div class="section" id="joints-1">
<h2>Joints (1)<a class="headerlink" href="#joints-1" title="Permalink to this headline">¶</a></h2>
<p>A static L shape is pretty boring. So lets make it a bit more exciting by
adding two joints, one that it can rotate around, and one that prevents it
from rotating too much. In this part we only add the rotation joint, and in
the next we constrain it. As our static L shape won&#8217;t be static anymore we
also rename the function to add_L().</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">add_L</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="n">rotation_center_body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span> <span class="c"># 1</span>
    <span class="n">rotation_center_body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>

    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">(</span><span class="mi">10</span><span class="p">,</span> <span class="mi">10000</span><span class="p">)</span> <span class="c"># 2</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>
    <span class="n">l1</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mf">255.0</span><span class="p">,</span> <span class="mf">0.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>
    <span class="n">l2</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mf">50.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>

    <span class="n">rotation_center_joint</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">PinJoint</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_body</span><span class="p">,</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">))</span> <span class="c"># 3</span>

    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">l1</span><span class="p">,</span> <span class="n">l2</span><span class="p">,</span> <span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_joint</span><span class="p">)</span>
    <span class="k">return</span> <span class="n">l1</span><span class="p">,</span><span class="n">l2</span>
</pre></div>
</div>
<p>#. This is the rotation center body. Its only purpose is to act as a static
point in the joint so the line can rotate around it. As you see we never add
any shapes to it.</p>
<p>#. The L shape will now be moving in the world, and therefor it can no
longer have infinite mass. I have precalculated the inertia to 10000.
(ok, I just took a number that worked, the important thing is that it looks
good on screen!).
#. A pin joint allow two objects to pivot about a single point. In our case
one of the objects will be stuck to the world.</p>
<p>To make it easy to see the point we draw a little red ball in its center</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;red&quot;</span><span class="p">],</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">),</span> <span class="mi">5</span><span class="p">)</span>
</pre></div>
</div>
<p>In a bigger program you will want to get the rotation_center_body.position
instead of my little cheat here with (300,300), but it will work for this
tutorial as the rotation center is static.</p>
</div>
<div class="section" id="joints-2">
<h2>Joints (2)<a class="headerlink" href="#joints-2" title="Permalink to this headline">¶</a></h2>
<p>In the previous part we added a pin joint, and now its time to constrain the
rotating L shape to create a more interesting simulation. In order to do this
we modify the add_L() function:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">add_L</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="n">rotation_center_body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span>
    <span class="n">rotation_center_body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>

    <span class="n">rotation_limit_body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span> <span class="c"># 1</span>
    <span class="n">rotation_limit_body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">200</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>

    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">(</span><span class="mi">10</span><span class="p">,</span> <span class="mi">10000</span><span class="p">)</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>
    <span class="n">l1</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mf">255.0</span><span class="p">,</span> <span class="mf">0.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>
    <span class="n">l2</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mf">50.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>

    <span class="n">rotation_center_joint</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">PinJoint</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_body</span><span class="p">,</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">))</span>
    <span class="n">joint_limit</span> <span class="o">=</span> <span class="mi">25</span>
    <span class="n">rotation_limit_joint</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">SlideJoint</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">rotation_limit_body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">100</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="mi">0</span><span class="p">,</span> <span class="n">joint_limit</span><span class="p">)</span> <span class="c"># 2</span>

    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">l1</span><span class="p">,</span> <span class="n">l2</span><span class="p">,</span> <span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_joint</span><span class="p">,</span> <span class="n">rotation_limit_joint</span><span class="p">)</span>
    <span class="k">return</span> <span class="n">l1</span><span class="p">,</span><span class="n">l2</span>
</pre></div>
</div>
<ol class="arabic simple">
<li>We add a body..</li>
</ol>
<p>#. Create a slide joint. It behaves like pin joints but have a minimum and
maximum distance. The two bodies can slide between the min and max, and in
our case one of the bodies is static meaning only the body attached with the
shapes will move.</p>
<p>And to make it a bit more clear, we draw a circle to do symbolize the joint
with a green circle with its radius set to the joint max:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;green&quot;</span><span class="p">],</span> <span class="p">(</span><span class="mi">200</span><span class="p">,</span><span class="mi">300</span><span class="p">),</span> <span class="mi">25</span><span class="p">,</span> <span class="mi">2</span><span class="p">)</span>
</pre></div>
</div>
</div>
<div class="section" id="the-end">
<h2>The end<a class="headerlink" href="#the-end" title="Permalink to this headline">¶</a></h2>
<p>You might notice that we never delete balls. This will make the simulation
require more and more memory and use more and more cpu, and this is of
course not what we want. So in the final step we add some code to remove
balls from the simulation when they are bellow the screen.</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">balls_to_remove</span> <span class="o">=</span> <span class="p">[]</span>
<span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls</span><span class="p">:</span>
    <span class="k">if</span> <span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">y</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="c"># 1</span>
        <span class="n">balls_to_remove</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">ball</span><span class="p">)</span> <span class="c"># 2</span>
    <span class="n">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">)</span>

<span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls_to_remove</span><span class="p">:</span>
    <span class="n">space</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">ball</span><span class="p">,</span> <span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="p">)</span> <span class="c"># 3</span>
    <span class="n">balls</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">ball</span><span class="p">)</span> <span class="c"># 4</span>
</pre></div>
</div>
<p>#. As we already have a loop we reuse it.. Check if the body.position is less
than 0.
#. If that is the case, we add it to our list of balls to remove.
#. To remove an object from the space, we need to remove its shape and its
body.
#. And then we remove it from our list of balls.</p>
<p>And now, done! You should have an inverted L shape in the middle of the
screen being filled will balls, tipping over releasing them, tipping back and
start over. You can check demo_slide_and_pinjoint.py included in pymunk, but
it doesn&#8217;t follow this tutorial exactly as I factored out a couple of blocks
to functions to make it easier to follow in tutorial form.</p>
<p>If anything is unclear, not working feel free to add a comment in the bottom
of the page. If you have an idea for another tutorial you want to read, or
some example code you want to see included in pymunk, please write it
somewhere (like in the chipmunk forum)</p>
<p>The full code for this tutorial is:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">import</span> <span class="nn">sys</span><span class="o">,</span> <span class="nn">random</span>
<span class="kn">import</span> <span class="nn">pygame</span>
<span class="kn">from</span> <span class="nn">pygame.locals</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">from</span> <span class="nn">pygame.color</span> <span class="kn">import</span> <span class="o">*</span>
<span class="kn">import</span> <span class="nn">pymunk</span>
<span class="kn">import</span> <span class="nn">math</span>

<span class="k">def</span> <span class="nf">to_pygame</span><span class="p">(</span><span class="n">p</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Small hack to convert pymunk to pygame coordinates&quot;&quot;&quot;</span>
    <span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">p</span><span class="o">.</span><span class="n">x</span><span class="p">),</span> <span class="nb">int</span><span class="p">(</span><span class="o">-</span><span class="n">p</span><span class="o">.</span><span class="n">y</span><span class="o">+</span><span class="mi">600</span><span class="p">)</span>

<span class="k">def</span> <span class="nf">add_ball</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Add a ball to the given space at a random position&quot;&quot;&quot;</span>
    <span class="n">mass</span> <span class="o">=</span> <span class="mi">1</span>
    <span class="n">radius</span> <span class="o">=</span> <span class="mi">14</span>
    <span class="n">inertia</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">moment_for_circle</span><span class="p">(</span><span class="n">mass</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="n">radius</span><span class="p">,</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">))</span>
    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">(</span><span class="n">mass</span><span class="p">,</span> <span class="n">inertia</span><span class="p">)</span>
    <span class="n">x</span> <span class="o">=</span> <span class="n">random</span><span class="o">.</span><span class="n">randint</span><span class="p">(</span><span class="mi">120</span><span class="p">,</span><span class="mi">380</span><span class="p">)</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="n">x</span><span class="p">,</span> <span class="mi">550</span>
    <span class="n">shape</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Circle</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">radius</span><span class="p">,</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">))</span>
    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">shape</span><span class="p">)</span>
    <span class="k">return</span> <span class="n">shape</span>

<span class="k">def</span> <span class="nf">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Draw a ball shape&quot;&quot;&quot;</span>
    <span class="n">p</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">x</span><span class="p">),</span> <span class="mi">600</span><span class="o">-</span><span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">y</span><span class="p">)</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;blue&quot;</span><span class="p">],</span> <span class="n">p</span><span class="p">,</span> <span class="nb">int</span><span class="p">(</span><span class="n">ball</span><span class="o">.</span><span class="n">radius</span><span class="p">),</span> <span class="mi">2</span><span class="p">)</span>

<span class="k">def</span> <span class="nf">add_L</span><span class="p">(</span><span class="n">space</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Add a inverted L shape with two joints&quot;&quot;&quot;</span>
    <span class="n">rotation_center_body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span>
    <span class="n">rotation_center_body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>

    <span class="n">rotation_limit_body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">()</span> <span class="c"># 1</span>
    <span class="n">rotation_limit_body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">200</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>

    <span class="n">body</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Body</span><span class="p">(</span><span class="mi">10</span><span class="p">,</span> <span class="mi">10000</span><span class="p">)</span>
    <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">=</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">)</span>
    <span class="n">l1</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">150</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mf">255.0</span><span class="p">,</span> <span class="mf">0.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>
    <span class="n">l2</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Segment</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="o">-</span><span class="mf">150.0</span><span class="p">,</span> <span class="mf">50.0</span><span class="p">),</span> <span class="mf">5.0</span><span class="p">)</span>

    <span class="n">rotation_center_joint</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">PinJoint</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_body</span><span class="p">,</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">))</span>
    <span class="n">joint_limit</span> <span class="o">=</span> <span class="mi">25</span>
    <span class="n">rotation_limit_joint</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">SlideJoint</span><span class="p">(</span><span class="n">body</span><span class="p">,</span> <span class="n">rotation_limit_body</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">100</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="mi">0</span><span class="p">,</span> <span class="n">joint_limit</span><span class="p">)</span> <span class="c"># 3</span>

    <span class="n">space</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">l1</span><span class="p">,</span> <span class="n">l2</span><span class="p">,</span> <span class="n">body</span><span class="p">,</span> <span class="n">rotation_center_joint</span><span class="p">,</span> <span class="n">rotation_limit_joint</span><span class="p">)</span>
    <span class="k">return</span> <span class="n">l1</span><span class="p">,</span><span class="n">l2</span>

<span class="k">def</span> <span class="nf">draw_lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">lines</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Draw the lines&quot;&quot;&quot;</span>
    <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span>
        <span class="n">body</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">body</span>
        <span class="n">pv1</span> <span class="o">=</span> <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">+</span> <span class="n">line</span><span class="o">.</span><span class="n">a</span><span class="o">.</span><span class="n">rotated</span><span class="p">(</span><span class="n">body</span><span class="o">.</span><span class="n">angle</span><span class="p">)</span>
        <span class="n">pv2</span> <span class="o">=</span> <span class="n">body</span><span class="o">.</span><span class="n">position</span> <span class="o">+</span> <span class="n">line</span><span class="o">.</span><span class="n">b</span><span class="o">.</span><span class="n">rotated</span><span class="p">(</span><span class="n">body</span><span class="o">.</span><span class="n">angle</span><span class="p">)</span>
        <span class="n">p1</span> <span class="o">=</span> <span class="n">to_pygame</span><span class="p">(</span><span class="n">pv1</span><span class="p">)</span>
        <span class="n">p2</span> <span class="o">=</span> <span class="n">to_pygame</span><span class="p">(</span><span class="n">pv2</span><span class="p">)</span>
        <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;lightgray&quot;</span><span class="p">],</span> <span class="bp">False</span><span class="p">,</span> <span class="p">[</span><span class="n">p1</span><span class="p">,</span><span class="n">p2</span><span class="p">])</span>


<span class="k">def</span> <span class="nf">main</span><span class="p">():</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">init</span><span class="p">()</span>
    <span class="n">screen</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_mode</span><span class="p">((</span><span class="mi">600</span><span class="p">,</span> <span class="mi">600</span><span class="p">))</span>
    <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_caption</span><span class="p">(</span><span class="s">&quot;Joints. Just wait and the L will tip over&quot;</span><span class="p">)</span>
    <span class="n">clock</span> <span class="o">=</span> <span class="n">pygame</span><span class="o">.</span><span class="n">time</span><span class="o">.</span><span class="n">Clock</span><span class="p">()</span>
    <span class="n">running</span> <span class="o">=</span> <span class="bp">True</span>

    <span class="n">space</span> <span class="o">=</span> <span class="n">pymunk</span><span class="o">.</span><span class="n">Space</span><span class="p">()</span>
    <span class="n">space</span><span class="o">.</span><span class="n">gravity</span> <span class="o">=</span> <span class="p">(</span><span class="mf">0.0</span><span class="p">,</span> <span class="o">-</span><span class="mf">900.0</span><span class="p">)</span>

    <span class="n">lines</span> <span class="o">=</span> <span class="n">add_L</span><span class="p">(</span><span class="n">space</span><span class="p">)</span>
    <span class="n">balls</span> <span class="o">=</span> <span class="p">[]</span>

    <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">10</span>
    <span class="k">while</span> <span class="n">running</span><span class="p">:</span>
        <span class="k">for</span> <span class="n">event</span> <span class="ow">in</span> <span class="n">pygame</span><span class="o">.</span><span class="n">event</span><span class="o">.</span><span class="n">get</span><span class="p">():</span>
            <span class="k">if</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">QUIT</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">elif</span> <span class="n">event</span><span class="o">.</span><span class="n">type</span> <span class="o">==</span> <span class="n">KEYDOWN</span> <span class="ow">and</span> <span class="n">event</span><span class="o">.</span><span class="n">key</span> <span class="o">==</span> <span class="n">K_ESCAPE</span><span class="p">:</span>
                <span class="n">running</span> <span class="o">=</span> <span class="bp">False</span>

        <span class="n">ticks_to_next_ball</span> <span class="o">-=</span> <span class="mi">1</span>
        <span class="k">if</span> <span class="n">ticks_to_next_ball</span> <span class="o">&lt;=</span> <span class="mi">0</span><span class="p">:</span>
            <span class="n">ticks_to_next_ball</span> <span class="o">=</span> <span class="mi">25</span>
            <span class="n">ball_shape</span> <span class="o">=</span> <span class="n">add_ball</span><span class="p">(</span><span class="n">space</span><span class="p">)</span>
            <span class="n">balls</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">ball_shape</span><span class="p">)</span>

        <span class="n">screen</span><span class="o">.</span><span class="n">fill</span><span class="p">(</span><span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;white&quot;</span><span class="p">])</span>

        <span class="n">balls_to_remove</span> <span class="o">=</span> <span class="p">[]</span>
        <span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls</span><span class="p">:</span>
            <span class="k">if</span> <span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="o">.</span><span class="n">position</span><span class="o">.</span><span class="n">y</span> <span class="o">&lt;</span> <span class="mi">150</span><span class="p">:</span>
                <span class="n">balls_to_remove</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">ball</span><span class="p">)</span>
            <span class="n">draw_ball</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">ball</span><span class="p">)</span>

        <span class="k">for</span> <span class="n">ball</span> <span class="ow">in</span> <span class="n">balls_to_remove</span><span class="p">:</span>
            <span class="n">space</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">ball</span><span class="p">,</span> <span class="n">ball</span><span class="o">.</span><span class="n">body</span><span class="p">)</span>
            <span class="n">balls</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">ball</span><span class="p">)</span>

        <span class="n">draw_lines</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">lines</span><span class="p">)</span>

        <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;red&quot;</span><span class="p">],</span> <span class="p">(</span><span class="mi">300</span><span class="p">,</span><span class="mi">300</span><span class="p">),</span> <span class="mi">5</span><span class="p">)</span>
        <span class="n">pygame</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">circle</span><span class="p">(</span><span class="n">screen</span><span class="p">,</span> <span class="n">THECOLORS</span><span class="p">[</span><span class="s">&quot;green&quot;</span><span class="p">],</span> <span class="p">(</span><span class="mi">200</span><span class="p">,</span><span class="mi">300</span><span class="p">),</span> <span class="mi">25</span><span class="p">,</span> <span class="mi">2</span><span class="p">)</span>

        <span class="n">space</span><span class="o">.</span><span class="n">step</span><span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">50.0</span><span class="p">)</span>

        <span class="n">pygame</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">flip</span><span class="p">()</span>
        <span class="n">clock</span><span class="o">.</span><span class="n">tick</span><span class="p">(</span><span class="mi">50</span><span class="p">)</span>

<span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&#39;__main__&#39;</span><span class="p">:</span>
    <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">(</span><span class="n">main</span><span class="p">())</span>
</pre></div>
</div>
</div>
</div>


          </div>
        </div>
      </div>
      <div class="sphinxsidebar">
        <div class="sphinxsidebarwrapper">
            <p class="logo"><a href="../index.html">
              <img class="logo" src="../_static/pymunk_logo_sphinx.png" alt="Logo"/>
            </a></p>
<h3><a href="../index.html">Table Of Contents</a></h3>
<ul class="current">
<li class="toctree-l1"><a class="reference internal" href="../readme.html">Readme</a></li>
<li class="toctree-l1"><a class="reference internal" href="../news.html">News</a></li>
<li class="toctree-l1"><a class="reference internal" href="../installation.html">Installation</a></li>
<li class="toctree-l1"><a class="reference internal" href="../pymunk.html">API Reference</a></li>
<li class="toctree-l1"><a class="reference internal" href="../examples.html">Examples</a></li>
<li class="toctree-l1 current"><a class="reference internal" href="../tutorials.html">Tutorials</a><ul class="current">
<li class="toctree-l2"><a class="reference internal" href="Arrows.html">Arrows and other pointy sticky things</a></li>
<li class="toctree-l2 current"><a class="current reference internal" href="">Slide and Pin Joint Demo Step by Step</a><ul>
<li class="toctree-l3"><a class="reference internal" href="#before-we-start">Before we start</a></li>
<li class="toctree-l3"><a class="reference internal" href="#an-empty-simulation">An empty simulation</a></li>
<li class="toctree-l3"><a class="reference internal" href="#falling-balls">Falling balls</a></li>
<li class="toctree-l3"><a class="reference internal" href="#a-static-l">A static L</a></li>
<li class="toctree-l3"><a class="reference internal" href="#joints-1">Joints (1)</a></li>
<li class="toctree-l3"><a class="reference internal" href="#joints-2">Joints (2)</a></li>
<li class="toctree-l3"><a class="reference internal" href="#the-end">The end</a></li>
</ul>
</li>
</ul>
</li>
<li class="toctree-l1"><a class="reference internal" href="../advanced.html">Advanced</a></li>
<li class="toctree-l1"><a class="reference external" href="http://code.google.com/p/pymunk/issues/list">Issue Tracker</a></li>
<li class="toctree-l1"><a class="reference external" href="http://code.google.com/p/pymunk/source/checkout">Source Repository</a></li>
<li class="toctree-l1"><a class="reference external" href="http://code.google.com/p/pymunk/downloads/list">Downloads</a></li>
<li class="toctree-l1"><a class="reference internal" href="../license.html">License</a></li>
</ul>

  <h4>Previous topic</h4>
  <p class="topless"><a href="Arrows.html"
                        title="previous chapter">Arrows and other pointy sticky things</a></p>
  <h4>Next topic</h4>
  <p class="topless"><a href="../advanced.html"
                        title="next chapter">Advanced</a></p>
  <h3>This Page</h3>
  <ul class="this-page-menu">
    <li><a href="../_sources/tutorials/SlideAndPinJoint.txt"
           rel="nofollow">Show Source</a></li>
  </ul>
<div id="searchbox" style="display: none">
  <h3>Quick search</h3>
    <form class="search" action="../search.html" method="get">
      <input type="text" name="q" />
      <input type="submit" value="Go" />
      <input type="hidden" name="check_keywords" value="yes" />
      <input type="hidden" name="area" value="default" />
    </form>
    <p class="searchtip" style="font-size: 90%">
    Enter search terms or a module, class or function name.
    </p>
</div>
<script type="text/javascript">$('#searchbox').show(0);</script>
        </div>
      </div>
      <div class="clearer"></div>
    </div>
    <div class="related">
      <h3>Navigation</h3>
      <ul>
        <li class="right" style="margin-right: 10px">
          <a href="../genindex.html" title="General Index"
             >index</a></li>
        <li class="right" >
          <a href="../py-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li class="right" >
          <a href="../advanced.html" title="Advanced"
             >next</a> |</li>
        <li class="right" >
          <a href="Arrows.html" title="Arrows and other pointy sticky things"
             >previous</a> |</li>
        <li><a href="../index.html">pymunk 4.0.0 documentation</a> &raquo;</li>
          <li><a href="../tutorials.html" >Tutorials</a> &raquo;</li> 
      </ul>
    </div>
    <div class="footer">
        &copy; Copyright 2013, Victor Blomqvist.
      Created using <a href="http://sphinx-doc.org/">Sphinx</a> 1.2b1.
    </div>
  </body>
</html>